package com.instance.demo2;

import java.lang.reflect.Array;
import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.lang.reflect.Modifier;

public class test {
	/**
	 * 通过class实例化其他类的对象
	 * 通过无参构造实例化对象（可以没有构造函数，如果有无参构造，必须提供无参构造）
	 * @throws Exception
	 */
	public void test1() throws Exception{
		Class<?> demo = Class.forName("com.instance.demo2.Person");
		Person p = null;
		p = (Person) demo.newInstance();
		p.setName("name");
		System.out.println(p);
	}
	/**
	 * 通过class调用其它类中的构造函数
	 * 通过class 创建其他类的对象
	 * @throws Exception
	 */
	public void test2()throws Exception{
		Class<?> demo = Class.forName("com.instance.demo2.Person");
        //取得全部的构造函数  
        Constructor<?> cons[]=demo.getConstructors();  
        System.out.println(cons[0].toString()+cons[1]+cons[2]+cons[3]);
        Person per1=(Person)cons[0].newInstance();  
        System.out.println(per1);  
        Person per2=(Person)cons[3].newInstance("ss");  
        System.out.println(per2);  
        Person per3=(Person)cons[1].newInstance(20);  
        System.out.println(per3);  
        Person per4=(Person)cons[2].newInstance("Rollen",20);  
        System.out.println(per4);  
	}
	/**
	 * 返回一个类实现的接口
	 * 取得其他类的父类
	 * @throws Exception
	 */
	public void test3()throws Exception{
		Class<?> demo = Class.forName("com.instance.demo2.Person");
		//保存所有的接口
		Class<?> intes[]=demo.getInterfaces();  
		//取得父类  
        Class<?> temp=demo.getSuperclass();  
		System.out.println("接口为：   "+intes.length+""+intes[0]);
		System.out.println("继承的父类为：   "+temp);
	}
	/**
	 * 通过class获取其他类全部构造函数
	 * @throws Exception
	 */
	public void test4()throws Exception{
		Class<?> demo = Class.forName("com.instance.demo2.Person");
        //取得全部的构造函数  
        Constructor<?> cons[]=demo.getConstructors(); 
        for(int i=0;i<cons.length;i++){
        	Class<?> p[] = cons[i].getParameterTypes();
        	System.out.print("构造方法：  ");  
        	int mo = cons[i].getModifiers();
        	System.out.print(mo);
        	System.out.print(Modifier.toString(mo)+" ");  
            System.out.print(cons[i].getName());  
            System.out.print("(");  
            for(int j=0;j<p.length;j++){
            	System.out.print(p[j]+" arg:"+i);
            	if(j!=p.length-1){
            		System.out.print(",");
            	}
            }
            System.out.println("){}");
        }
	}
	/**
	 * 通过class获取其他类的方法（包括异常）
	 * @throws Exception
	 */
	public void test5()throws Exception{
		Class<?> demo = Class.forName("com.instance.demo2.Person");
		Method method[]=demo.getMethods();  
		for(int i=0;i<method.length;i++){
			Class<?> returnType = method[i].getReturnType();
			Class<?> para[] = method[i].getParameterTypes();
			Class<?> exec[] = method[i].getExceptionTypes();
			int temp = method[i].getModifiers();
			System.out.print("方法：  "+temp);
			System.out.print(Modifier.toString(temp)+" ");
			System.out.print(returnType.getName()+" ");
			System.out.print(method[i].getName()+" (");
			for(int j=0;j<para.length;j++){
				System.out.print(para[j].getName()+" arg:"+j);
				if(j!=para.length-1){
            		System.out.print(",");
            	}
			}
			if(exec.length>0){
				System.out.print(") throws ");
				for(int k=0;k<exec.length;k++){
					System.out.print(exec[k].getName()+" ");
					if(k!=exec.length-1){
						System.out.print(",");
					}
				}
			}else{
				System.out.print(")");
			}
			System.out.println();
		}
	}
	/**
	 * 通过class取得其他类的属性
	 * @throws Exception
	 */
	public void test6()throws Exception{
		Class<?> demo = Class.forName("com.instance.demo2.Person");
		//获取本类的全部属性
		Field[] field = demo.getDeclaredFields();
		System.out.println("===============本类属性========================");
		for(int i = 0; i < field.length; i++){
			// Field的getModifiers()方法返回int类型值表示该字段的修饰符  
            int mo = field[i].getModifiers(); 
            String priv = Modifier.toString(mo);  
            // 属性类型  
            Class<?> type = field[i].getType();  
            System.out.println(priv + " " + type.getName() + " "  
                    + field[i].getName() + ";");  
		}
		 System.out.println("===============实现的接口或者父类的属性========================");  
		// 取得实现的接口或者父类的属性  
		Field[] filed1 = demo.getFields();  
		for (int j = 0; j < filed1.length; j++) {  
		    // 权限修饰符  
		int mo = filed1[j].getModifiers();  
		String priv = Modifier.toString(mo);  
		// 属性类型  
		Class<?> type = filed1[j].getType();  
		System.out.println(priv + " " + type.getName() + " "  
		+ filed1[j].getName() + ";");  
		}  
	}
	/**
	 * 通过class调用其它类的方法
	 * @throws Exception
	 */
	public void test7()throws Exception{
		Class<?> demo = Class.forName("com.instance.demo2.Person");
		//调用Person类中的sayChina方法  
        Method method=demo.getMethod("sayChina");  
        method.invoke(demo.newInstance());  
        //调用Person的sayHello方法  
//        Method method2=demo.getMethod("sayHello", String.class,int.class);  
//        Method method2=demo.getDeclaredMethod("sayHello", String.class,int.class);  
        Method method2=demo.getMethod("sayHello", new Class[]{String.class,int.class});  
        method2.invoke(demo.newInstance(),"Rollen",20);  
	}
	/**
	 * 通过class调用其他类的getter setter方法
	 * @throws Exception
	 */
	public void test8()throws Exception{
		Class<?> demo = Class.forName("com.instance.demo2.Person");
		Object obj = demo.newInstance();
		setter(obj, "Name","jack", String.class);
		getter(obj, "Name");
		System.out.println(obj);
	}
	/**
	 * 通过class 操作其他类的属性（）
	 * @throws Exception
	 */
	public void test9()throws Exception{
		Class<?> demo = Class.forName("com.instance.demo2.Person");
		Object obj = demo.newInstance();
		Field field = demo.getDeclaredField("name");
		field.setAccessible(true);//设置私有属性可以访问
		field.set(obj, "jack");
		System.out.println(obj);
	}
	/**
	 * 通过反射获取并修改数组的信息
	 */
	public void test10(){
		int[] temp={1,2,3,4,5};  
        Class<?>demo=temp.getClass().getComponentType();  
        System.out.println("数组类型： "+demo.getName());  
        System.out.println("数组长度  "+Array.getLength(temp));  
        System.out.println("数组的第一个元素: "+Array.get(temp, 0));  
        Array.set(temp, 0, 100);  
        System.out.println("修改之后数组第一个元素为： "+Array.get(temp, 0));  
	}
	/**
	 * 通过反射修改数组大小
	 */
	public void test11(){
		int[] temp={1,2,3,4,5,6,7,8,9};  
        int[] newTemp=(int[])arrayInc(temp,15);  
        print(newTemp);  
        System.out.println("=====================");  
        String[] atr={"a","b","c"};  
        String[] str1=(String[])arrayInc(atr,8);  
        print(str1);  
	}
	/**
	 * 获取类加载器
	 */
	public void test12(){
		test t=new test();  
        System.out.println("类加载器  "+t.getClass().getName());  
        System.out.println("类加载器  "+t.getClass().getClassLoader().getClass().getName());  
	}
	/**
	 * 获取实例的属性和值
	 * @throws IllegalAccessException 
	 * @throws IllegalArgumentException 
	 */
	public void test13() throws Exception{
		Person p = new Person("jack", 23);
		Class<?> demo = p.getClass(); 
		//获取本类的全部属性
		Field[] field = demo.getDeclaredFields();
		System.out.println("===============本类属性========================");
		for(int i = 0; i < field.length; i++){
			// Field的getModifiers()方法返回int类型值表示该字段的修饰符  
            int mo = field[i].getModifiers(); 
            String priv = Modifier.toString(mo);  
            // 属性类型 
            Class<?> type = field[i].getType();  
            field[i].setAccessible(true); //设置些属性是可以访问的  
            Object val = field[i].get(p);//得到此属性的值     
            System.out.println(field[i].getName() + ":"+val);  
		}
	}
	public static void main(String[] args) throws Exception {
//		new test().test1();
//		new test().test2();
//		new test().test3();
//		new test().test4();
//		new test().test5();
//		new test().test6();
//		new test().test7();
//		new test().test8();
//		new test().test9();
//		new test().test10();
//		new test().test11();
//		new test().test12();
		new test().test13();
		
	}
	/**
	 * @param obj 操作对象
	 * @param att 对象的属性
	 * @param value set的值
	 * @param type 参数的类型
	 * @throws Exception
	 */
	public void setter(Object obj,String att,Object value,Class<?> type) throws Exception{
		Method method = obj.getClass().getMethod("set"+att,type);
		method.invoke(obj, value); 
	}
	/**
	 * 
	 * @param obj 操作对象
	 * @param att 操作的属性
	 * @throws Exception
	 */
	public void getter(Object obj,String att)throws Exception{
		Method method = obj.getClass().getMethod("get"+att);
		System.out.println(method.invoke(obj)); 
	}
	/** 
     * 修改数组大小 
     */  
    public static Object arrayInc(Object obj,int len){  
        Class<?>arr=obj.getClass().getComponentType();  
        Object newArr=Array.newInstance(arr, len);  
        int co=Array.getLength(obj);  
        System.arraycopy(obj, 0, newArr, 0, co);  
        return newArr;  
    }  
    /** 
     * 打印 
     */  
    public static void print(Object obj){  
        Class<?>c=obj.getClass();  
        if(!c.isArray()){  
            return;  
        }  
        System.out.println("数组长度为： "+Array.getLength(obj));  
        for (int i = 0; i < Array.getLength(obj); i++) {  
            System.out.print(Array.get(obj, i)+" ");  
        }  
    }  
}
